﻿using System;
using System.Data;
using System.Configuration;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.HtmlControls;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Xml.Linq;
using System.Collections.Generic;

using ProjectMadaktariMVC.Models;

namespace ProjectMadaktariMVC.Controllers
{
    [Authorize]
    public class PatientController : Controller
    {

        // HTTP-GET: /Patient/
        public void Index()
        {
            Response.Write("<h1>Hello World</h2>");
        }

        public ActionResult New()
        {
            Patient patient = new Patient();
            return View(patient);
        }

        [AcceptVerbs(HttpVerbs.Post)]
        public ActionResult New(Patient patient)
        {
            PatientDAO patientDAO = new PatientDAO();
            try
            {
                if (patient.IsValid)
                {
                    if (patient.Id == 0)
                    {
                        patientDAO.Add(patient);
                    }
                    patientDAO.Save();
                    return RedirectToAction("View", new { id = patient.Id });
                }
                else
                {

                    foreach (var issue in patient.GetRuleViolations())
                    {
                        ModelState.AddModelError(issue.PropertyName, issue.ErrorMessage);
                    }
                    return View(patient);
                }
            }
            catch
            {
                patientDAO.Delete(patient);
                foreach (var issue in patient.GetRuleViolations())
                {
                    ModelState.AddModelError(issue.PropertyName, issue.ErrorMessage);
                }

                return View(patient);
            }
        }

        public ActionResult Find()
        {
            return View();
        }

        [AcceptVerbs(HttpVerbs.Post)]
        public ActionResult Find(FormCollection formValues)
        {
            PatientDAO patientDAO = new PatientDAO();

            //pulls out string to get.
            string fname = formValues.Get("fname");
            string lname = formValues.Get("lname");
            string registrationNumber = formValues.Get("registrationNumber");
            string ageGroup = formValues.Get("ageGroup");

            ViewData["fname"] = fname;
            ViewData["lname"] = lname;
            ViewData["registrationNumber"] = registrationNumber;
            ViewData["ageGroup"] = ageGroup;

            //Send that info to DAO
            //Returns a list of patients

            List<Patient> patientList = patientDAO.FindPatient(fname, lname, registrationNumber, ageGroup); //Method to search

            ViewData["patientList"] = patientList;

            return View("FindResults");
        }

        public ActionResult View(int id)
        {
            PatientDAO patientDAO = new PatientDAO();
            Patient patient = patientDAO.GetPatient(id);
            return View(patient);
        }

        public ActionResult Edit(int id)
        {
            PatientDAO patientDAO = new PatientDAO();
            Patient patient = patientDAO.GetPatient(id);
            return View(patient);
        }

        [AcceptVerbs(HttpVerbs.Post)]
        public ActionResult Edit(int id, FormCollection formValues)
        {
            PatientDAO patientDAO = new PatientDAO();

            Patient patient = patientDAO.GetPatient(id);

            UpdateModel(patient);

            if (patient.IsValid)
            {
                patientDAO.Save();
                return RedirectToAction("View", new { id = patient.Id });
            }
            else
            {
                foreach (var issue in patient.GetRuleViolations())
                {
                    ModelState.AddModelError(issue.PropertyName, issue.ErrorMessage);
                }
                return View(patient);
            }
        }

        public ActionResult AddEpisode(int id)
        {
            PatientDAO patientDAO = new PatientDAO();
            Patient patient = patientDAO.GetPatient(id);

            Episode episode = new Episode();

            ViewData["episode"] = episode;
            ViewData["PatientId"] = id;

            return View(patient);

        }

        [AcceptVerbs(HttpVerbs.Post)]
        public ActionResult AddEpisode(int id, Episode episode, FormCollection formValues)
        {
            using (var db = DBFactory.CreateContext())
            {
                PatientDAO patientDAO = new PatientDAO();
                Patient patient = patientDAO.GetPatient(id);
                PopulateEpisode(db, episode, formValues);
                patient.Episodes.Add(episode);
                patientDAO.Save();

                return Redirect(Url.Action("ViewEpisode", new { PatientId = patient.Id, EpisodeId = patient.Episodes.Last().Id }) + "#" + formValues.Get("tab"));
            }
        }

        public ActionResult EditEpisode(int PatientId, int EpisodeId)
        {
            PatientDAO patientDAO = new PatientDAO();
            Patient patient = patientDAO.GetPatient(PatientId);
            Episode episode = patient.Episodes.Single(e => e.Id == EpisodeId);
            ViewData["episode"] = episode;
            ViewData["PatientId"] = PatientId;
            return View(patient);
        }

        [AcceptVerbs(HttpVerbs.Post)]
        public ActionResult EditEpisode(int PatientId, int EpisodeId, FormCollection formValues)
        {
            using (var db = DBFactory.CreateContext())
            {
                PatientDAO patientDAO = new PatientDAO();
                Patient patient = patientDAO.GetPatient(PatientId);
                Episode episode = patientDAO.GetEpisode(EpisodeId);
                PopulateEpisode(db, episode, formValues);
                patientDAO.Save();

                return Redirect(Url.Action("ViewEpisode", new { PatientId = PatientId, EpisodeId = EpisodeId }) + "#" + formValues.Get("tab"));
            }
        }

        public ActionResult ViewEpisode(int PatientId, int EpisodeId)
        {
            PatientDAO patientDAO = new PatientDAO();
            Patient patient = patientDAO.GetPatient(PatientId);

            var episode = patient.Episodes.Single(e => e.Id == EpisodeId);

            ViewData["episode"] = episode;

            return View(patient);
        }



        public ActionResult AddProcedure(int EpisodeId)
        {
            PatientDAO patientDAO = new PatientDAO();
            Episode episode = patientDAO.GetEpisode(EpisodeId);

            ViewData["procedure"] = new Procedure();
            ViewData["episode"] = episode;

            return View(episode);

        }

        [AcceptVerbs(HttpVerbs.Post)]
        public ActionResult AddProcedure(int EpisodeId, Procedure procedure, FormCollection formValues)
        {
            PatientDAO patientDAO = new PatientDAO();
            Episode episode = patientDAO.GetEpisode(EpisodeId);

            UpdateModel(procedure);
            episode.Procedures.Add(procedure);

            patientDAO.Save();

            return Redirect(Url.Action("ViewEpisode", new { EpisodeId = episode.Id, PatientId = episode.PatientId }) + "#Procedure");
        }

        public ActionResult EditProcedure(int procedureId)
        {
            PatientDAO patientDAO = new PatientDAO();
            Procedure procedure = patientDAO.GetProcedure(procedureId);
            ViewData["episode"] = procedure.Episode;
            return View(procedure);
        }

        [AcceptVerbs(HttpVerbs.Post)]
        public ActionResult EditProcedure(int procedureId, FormCollection formValues)
        {
            PatientDAO patientDAO = new PatientDAO();
            Procedure procedure = patientDAO.GetProcedure(procedureId);
            UpdateModel(procedure);
            patientDAO.Save();
            return Redirect(Url.Action("ViewEpisode", new { EpisodeId = procedure.EpisodeId, PatientId = procedure.Episode.PatientId }) + "#Procedure");
        }


        private void PopulateEpisode(MadaktariDataContext db, Episode episode, FormCollection formValues)
        {
            PatientDAO patientDAO = new PatientDAO();
            if (formValues.Get("dischargeDate") != null && formValues.Get("dischargeDate").Trim() != "")
                episode.DischargeDate = DateTime.Parse(formValues.Get("dischargeDate"));
            if (formValues.Get("admitDate") != null && formValues.Get("admitDate").Trim() != "")
                episode.AdmitDate = DateTime.Parse(formValues.Get("admitDate"));
            episode.CaseComments = formValues.Get("caseComments");
            episode.ComplicationNotes = formValues.Get("complicationsNotes");
            if (formValues.Get("complications") != null && formValues.Get("complications").Trim() != "")
                episode.Complications = bool.Parse(formValues.Get("complications"));
            if (formValues.Get("followUpDate") != null && formValues.Get("followUpDate").Trim() != "")
                episode.FollowUpDate = DateTime.Parse(formValues.Get("followUpDate"));
            episode.FollowUpStatus = formValues.Get("followUpStatus");
            if (formValues.Get("HospitalId") != null && formValues.Get("HospitalId").Trim() != "")
                episode.HospitalId = int.Parse(formValues.Get("HospitalId"));
            episode.ImageFindings = formValues.Get("imageFindings");
            episode.PostOpStatus = formValues.Get("postOpStatus");
            if (formValues.Get("referralLocationID") != null && formValues.Get("referralLocationID").Trim() != "")
                episode.ReferralLocationId = int.Parse(formValues.Get("referralLocationID"));
            if (formValues.Get("concomitantDiagnosis1ID") != null && formValues.Get("concomitantDiagnosis1ID").Trim() != "")
                episode.ConcomitantDiagnosi = ConfigurationDAO.GetConcomitantDiagnosis(db, int.Parse(formValues.Get("concomitantDiagnosis1ID")));
            if (formValues.Get("concomitantDiagnosis2ID") != null && formValues.Get("concomitantDiagnosis2ID").Trim() != "")
                episode.ConcomitantDiagnosi1 = ConfigurationDAO.GetConcomitantDiagnosis(db, int.Parse(formValues.Get("concomitantDiagnosis2ID")));
            episode.DiagnosisOther = formValues.Get("diagnosisOther");
            var diagnoses = formValues.Get("diagnoses");
            if (diagnoses == null)
            {
                episode.EpisodeDiagnosisRelationships.Clear();
            }
            else
            {
                var newList = diagnoses.Split(',').ToList();
                for (var i = 0; i < episode.EpisodeDiagnosisRelationships.Count; i++)
                {
                    var rel = episode.EpisodeDiagnosisRelationships.ElementAt(i);
                    if (newList.Contains(rel.DiagnosisId.ToString()))
                    {
                        newList.Remove(rel.DiagnosisId.ToString());
                    }
                    else
                    {
                        patientDAO.RemoveEpisodeDiagnosisRelationship(rel);
                    }
                }

                foreach (String s in newList)
                {
                    var dId = int.Parse(s);
                    EpisodeDiagnosisRelationship rel = new EpisodeDiagnosisRelationship();
                    rel.DiagnosisId = dId;
                    episode.EpisodeDiagnosisRelationships.Add(rel);
                }
            }
            episode.SurgicalHistory = formValues.Get("surgicalHistory");
        }
    }
}
